/**
******************************************************************************
* @file    qmsg.h
* @author  Lucien
* @version V1.0.0
* @date    10/31/2018
* @brief
******************************************************************************
* @attention
*
*
*
******************************************************************************
*/
#ifndef __QMSG_H__
#define __QMSG_H__
#include <stdint.h>
#include <stddef.h>


#define OS_ERR_Q_EMPTY                  3u      // FIFO is empty
#define OS_ERR_Q_FULL                   2u      // FIFO is full
#define OS_ERR_INVALID_PARAM            1u      // Input invalid param
#define OS_ERR_NONE                     0u      // None error

#define MSG_BUF_SIZE                    150u

/* msg handler type */
typedef void(*msg_handler_t)(void *param);

/* msg instance type*/
typedef struct _tag_msg_t
{
    void*   param;
    msg_handler_t handler;
} msg_t;

typedef struct _tag_os_q
{
    msg_t            *osq_start;            /* Pointer to start of queue data                              */
    msg_t            *osq_end;              /* Pointer to end   of queue data                              */
    msg_t            *osq_in;               /* Pointer to where next message will be inserted  in   the Q  */
    msg_t            *osq_out;              /* Pointer to where next message will be extracted from the Q  */
    uint16_t          osq_size;             /* Size of queue (maximum number of entries)                   */
    uint16_t          osq_entries;          /* Current number of entries in the queue                      */
    msg_t *           *pmsgGrp;
    uint16_t          msg_size;
} OS_Q;


typedef struct _tag_queue_msg
{
    OS_Q              q_msg;
    msg_t*            msgGrp;
    uint16_t          msg_size;
} queue_msg_t;


/**
* @brief   Create msg queue
* */
void msg_init(queue_msg_t *msg_head, msg_t* msgGrp, uint16_t grp_size);

/* Post a msg to a msg queue tail, which can be executed in a right place */
uint16_t msg_post(queue_msg_t *msg_head, msg_handler_t handler, void *arg);

/*  Post a msg to a msg queue front, which can be executed in a right place */
uint16_t msg_post_front(queue_msg_t *msg_head, msg_handler_t handler, void *arg);

/* accept a msg form queue */
uint16_t msg_post_accept(queue_msg_t *msg_head, msg_t *pmsg);

/**
* @brief msg schedule ,from queue take one msg(handler) to execute.
* */
// uint8_t msg_schedule(queue_msg_t *msg_head);




#endif
